/**
 * @description 改变字符串形式，大驼峰和小驼峰形式
 * @param {String} str 字符串
 * @param {String} type 类型--默认值：'camel' 默认小驼峰形式。  可选值： 'pascal'和'camel'   含义说明： 'pascal'：大驼峰形式，  'camel'：小驼峰形式。
 * @returns {String} {String}
 * @example
 * ::: demo
 *
 * ```html
 *  <template>
 *   <div>
 *    <p><b>小驼峰形式：</b>{{ changeCase }}</p>
 *    <p><b>大驼峰形式：</b>{{ changeCase1 }}</p>
 *   </div>
 *  </template>
 *  <script>
 *    export default {
 *      data() {
 *        return {
 *          changeCase: '',
 *          changeCase1: ''
 *        }
 *    },
 *    mounted() {
 *      this.changeCase = this.$portal.changeCase('is-png')
 *      this.changeCase1 = this.$portal.changeCase('is-png', 'pascal')
 *    }
 *  }
 *  </script>
 *
 * ```
 * :::
 *
 */

function splitStr(str: string): Array<string> {
  const rtv: Array<Array<string>> = []

  for (let i = 0; i < str.length; i++) {
    const item: string = str[i]

    if (i === 0 || /[A-Z]/.test(item)) {
      rtv.push([])
    }

    rtv[rtv.length - 1].push(item.toLocaleLowerCase())
  }

  return rtv.map((x) => x.join(''))
}

function noCase(str: string): Array<string> {
  return str && str.split
    ? str.split(/[\W_]/g).reduce((prev: any, item) => {
        prev = [...prev, ...splitStr(item)]
        return prev
      }, [])
    : []
}

export default function (str: string, type = 'camel') {
  if (type === 'camel') {
    // "test string" => "testString"
    return noCase(str)
      .map((x, index) => (index === 0 ? x : x.replace(/^[a-z]/, ($0) => $0.toUpperCase())))
      .join('')
  }

  if (type === 'capital') {
    // "test string" => "Test String"
    return noCase(str)
      .map((x) => x.replace(/^[a-z]/, ($0) => $0.toUpperCase()))
      .join(' ')
  }

  if (type === 'constant') {
    // "test string" => "Test_String"
    return noCase(str)
      .map((x) => x.toUpperCase())
      .join('_')
  }

  if (type === 'dot') {
    // "test string" => "test.string"
    return noCase(str).join('.')
  }

  if (type === 'header') {
    // "test string" => "Test-String"
    return noCase(str)
      .map((x) => x.replace(/^[a-z]/, ($0) => $0.toUpperCase()))
      .join('-')
  }

  if (type === 'no') {
    // "test string" => "Test-String"
    return noCase(str).join(' ')
  }

  if (type === 'param' || type === 'kebab') {
    // "test string" => "test-string"
    return noCase(str).join('-')
  }

  if (type === 'pascal') {
    // "test string" => "TestString"
    return noCase(str)
      .map((x) => x.replace(/^[a-z]/, ($0) => $0.toUpperCase()))
      .join('')
  }

  if (type === 'path') {
    // "test string" => "test/string"
    return noCase(str).join('/')
  }

  if (type === 'sentence') {
    // "testString" => "Test string"
    return noCase(str)
      .map((x, index) => (index === 0 ? x.replace(/^[a-z]/, ($0) => $0.toUpperCase()) : x))
      .join(' ')
  }

  if (type === 'snake') {
    // "test string" => "test_string"
    return noCase(str).join('_')
  }

  return str
}
